package com.goldgov.conference.service.impl;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.goldgov.conference.dao.ConferenceDao;
import com.goldgov.conference.dao.ConferenceStatDao;
import com.goldgov.conference.service.Conference;
import com.goldgov.conference.service.ConferenceStat;
import com.goldgov.conference.service.ConferenceStatQuery;
import com.goldgov.conference.service.ConferenceStatService;
import com.goldgov.meetingstatistics.bean.MeetingParamsBean;
import com.goldgov.synchronous.service.ConferenceSynchronous;
import com.goldgov.utils.DateUtil;
import com.goldgov.utils.PropertyUtil;

/** 
 * @ClassName: ConferenceStatServiceImpl 
 * @Description: TODO
 * @author hanxiangyu
 * @date 2018年6月19日 下午7:41:33 
 */
@Service
public class ConferenceStatServiceImpl implements ConferenceStatService {

	@Autowired
	private ConferenceStatDao conferenceStatDao;
	
	@Autowired
	private ConferenceDao conferenceDao;
	
	
	
	/**
	 * 支部首页统计 START
	 */
	/**
	 * 当前登录党员所在支部统计
	 * @date 2018年8月24日 下午2:50:15 
	 * @author hanxiangyu
	 * @param conferenceStat
	 * @return
	 */
	public ConferenceStat getPortalPartyBranchStat(ConferenceStat conferenceStat) {
		ConferenceStat con = conferenceStatDao.getPortalPartyBranchStat(conferenceStat);
		if (con.getYearSunNum() == null) {
			con.setYearSunNum(con.getZbdyNum() + con.getDkSunNum() + con.getDzbwyhSunNum() + con.getDxzSunNum());
		}
		//获取本季度会议数量
		ConferenceStat conferenceStatqu = new ConferenceStat();
		conferenceStatqu.setUserID(conferenceStat.getUserID());
		conferenceStatqu.setYear(conferenceStat.getYear());
		conferenceStatqu.setQuarter(DateUtil.getSeason(new Date()));
		ConferenceStat con1 = conferenceStatDao.getPortalPartyBranchStat(conferenceStatqu);
		con.setQuarterSunNum(con1.getZbdyNum() + con1.getDkSunNum() + con1.getDzbwyhSunNum() + con1.getDxzSunNum());
		return con;
	}
	
	
	/**
	 * 同级党支部排行情况统计
	 * @date 2018年6月20日 下午3:54:57 
	 * @author hanxiangyu
	 * @param conferenceStat
	 * @return
	 */
	public List<ConferenceStat> getPortalPartyORankStat(ConferenceStatQuery query){
		return conferenceStatDao.getPortalPartyORankStat(query);
	}
	
	
	
	/**
	 * 支部首页统计 END
	 */
	
	
	
	
	/** 
	 * @Description: 本支部组织生活统计分析
	 * @author hanxiangyu
	 * @date 2018年6月19日 下午7:42:05 
	 */
	@Override
	public ConferenceStat getPartyOrganizationLife(ConferenceStat conferenceStat) {
		//获取本年度总会议数和各种会议数量
		ConferenceStat con = conferenceStatDao.getPartyOrganizationLife(conferenceStat);
		if (con.getYearSunNum() == null) {
			con.setYearSunNum(con.getZbdyNum() + con.getDkSunNum() + con.getDzbwyhSunNum() + con.getDxzSunNum());
		}
		//获取本季度会议数量
		ConferenceStat conferenceStatqu = new ConferenceStat();
		conferenceStatqu.setScopeCode(conferenceStat.getScopeCode());
		conferenceStatqu.setYear(conferenceStat.getYear());
		conferenceStatqu.setQuarter(DateUtil.getSeason(new Date()));
		ConferenceStat con1 = conferenceStatDao.getPartyOrganizationLife(conferenceStatqu);
		con.setQuarterSunNum(con1.getZbdyNum() + con1.getDkSunNum() + con1.getDzbwyhSunNum() + con1.getDxzSunNum());
		return con;
	}

	/** 
	 * @Description: 会议出勤情况
	 * @author hanxiangyu
	 * @date 2018年6月20日 上午9:58:27 
	 */
	@Override
	public ConferenceStat getAttenanceStat(ConferenceStat conferenceStat) {
		ConferenceStat attenanceStat = conferenceStatDao.getAttenanceStat(conferenceStat);
		if (attenanceStat != null) {
			attenanceStat.setNoSignNum(attenanceStat.getJoinNum() - attenanceStat.getLeaveNum() - attenanceStat.getSignNum());
		}
		return attenanceStat;
	}

	/** 
	 * @Description: 同级党支部排行情况统计
	 * @author hanxiangyu
	 * @date 2018年6月20日 下午3:55:56 
	 */
	@Override
	public List<ConferenceStat> getPartyOrganizationRank(ConferenceStatQuery query) {
		return conferenceStatDao.getPartyOrganizationRank(query);
	}

	/** 
	 * @Description: TODO
	 * @author hanxiangyu
	 * @date 2018年6月25日 下午2:06:15 
	 */
	@Override
	public List<ConferenceStat> getPartyOrganizationByAdmin(ConferenceStatQuery query) {
		return conferenceStatDao.getPartyOrganizationByAdmin(query);
	}

	/** 
	 * @Description: TODO
	 * @author hanxiangyu
	 * @date 2018年7月20日 上午9:53:56 
	 */
	@Override
	public List<ConferenceStat> getBranchStudy(ConferenceStatQuery query) {
		List<ConferenceStat> list = conferenceStatDao.getBranchStudy(query);
		for (ConferenceStat attenanceStat : list) {
			attenanceStat.setNoSignNum(attenanceStat.getJoinNum() - attenanceStat.getLeaveNum() - attenanceStat.getSignNum());
			Conference c = new Conference();
			c.setConferenceID(attenanceStat.getConferenceID());
			c.setUserID(query.getSearchUserID());
			Conference userStates = conferenceDao.getUserStates(c);
			if (userStates == null) {
				attenanceStat.setUserStatus(3);	//未参加
			}else {
				attenanceStat.setUserStatus(userStates.getUserStatus());
			}
		}
		return list;
	}

	@Override
	public List<ConferenceStat> findPartyOrganizationLife(ConferenceStatQuery query) {
		//获取本年度总会议数和各种会议数量
				List<ConferenceStat> list = conferenceStatDao.findPartyOrganizationLife(query);
				int orgCount=conferenceStatDao.findOrgNum(query.getSearchScopeCode());
				//con.getZbdyNum() + con.getDkSunNum() + con.getDzbwyhSunNum() + con.getDxzSunNum()
				
				for(ConferenceStat con :list) {
					if(con.getZbdyNum()>0) con.setZbdyAvgNum(new BigDecimal((double)con.getZbdyNum()/(double)orgCount).setScale(1, RoundingMode.UP).doubleValue() );
					if(con.getDxzSunNum()>0) con.setDxzAvgNum(new BigDecimal((double)con.getDxzSunNum()/(double)orgCount).setScale(1, RoundingMode.UP).doubleValue() );
					if(con.getDzbwyhSunNum()>0) con.setDzbwyhAvgNum(new BigDecimal((double)con.getDzbwyhSunNum()/(double)orgCount).setScale(1, RoundingMode.UP).doubleValue() );
					if(con.getDkSunNum()>0) con.setDkAvgNum(new BigDecimal((double)con.getDkSunNum()/(double)orgCount).setScale(1, RoundingMode.UP).doubleValue() );
				}
				return list;
	}


	@Override
	public List<ConferenceStat> countConferencePercentage(ConferenceStatQuery query) {
		
		List<ConferenceStat> list=conferenceStatDao.countConferencePercentage(query);
		DecimalFormat df = new DecimalFormat("0.00%");//格式化小数 
		int proportion=1;
		Date date=new Date();
		//如果只选年，查看是否当年，不是当年的修改除数季度或月值
		if((ConferenceStatQuery.ZBDYDH.equals(Integer.valueOf(query.getSearchType()))
				||ConferenceStatQuery.ZBWYHHY.equals(Integer.valueOf(query.getSearchType())))
				&&(query.getSearchQuarter()==null||query.getSearchQuarter()<=0)) {
			
			if(String.valueOf(DateUtil.getYear(date)).equals(query.getSearchYear())) {
				proportion=DateUtil.getSeason(date);
			}else {
				proportion=4;
			}
			
		}else if((ConferenceStatQuery.DXZH.equals(Integer.valueOf(query.getSearchType()))
				||ConferenceStatQuery.DK.equals(Integer.valueOf(query.getSearchType())))
				&&(query.getSearchMonth()==null||query.getSearchMonth()<=0)
				) {
			if(String.valueOf(DateUtil.getYear(date)).equals(query.getSearchYear())) {
				proportion=DateUtil.getMonth(date);
			}else {
				proportion=12;
			}
		}
		
		for(ConferenceStat bean :list) {
			if(PropertyUtil.objectNotEmpty(bean.getSunNum())&&bean.getSunNum()>0) {
				bean.setAvgReachNum(df.format((double)bean.getSunNum()/(bean.getOrgNum()*query.getSearchReachConferenceNum()*proportion)));
			}else {
				bean.setAvgReachNum("0%");
			}
		}
		return list;
	}


	@Override
	public List<ConferenceStat> countConferenceAttachPercentage(ConferenceStatQuery query) {
		query.setPageSize(-1);
		ConferenceStat conferenceStat=conferenceStatDao.countConferenceAttachPercentage(query);
		if(!PropertyUtil.objectNotEmpty(conferenceStat)) {
			conferenceStat=new ConferenceStat();
			conferenceStat.setAttachOrder("0,0,0,0,0,0,0,0");//没有数据时初始化为0
		}
		String [] attachNums=conferenceStat.getAttachOrder().split(",");
		//求和
		int totCount=0;
		for(String num:attachNums) {
			totCount+=Integer.parseInt(num);
		}
		//计算
		DecimalFormat df = new DecimalFormat("0.00%");//格式化小数 
		List<ConferenceStat> list=new ArrayList<ConferenceStat>();
		for(int i=1;i<=attachNums.length;i++) {
			ConferenceStat bean=new ConferenceStat();
			bean.setSunNum(totCount);
			bean.setAttachNum(Integer.valueOf(attachNums[i-1]));
			bean.setAttachOrder(String.valueOf(i));
			if(bean.getAttachNum()>0&&bean.getSunNum()>0) {
				bean.setAvgReachNum(df.format((double)bean.getAttachNum()/(double)bean.getSunNum()));
			}else {
				bean.setAvgReachNum("0%");
			}
			list.add(bean);
		}
		return list;
	}


	@Override
	public List<ConferenceStat> countConferencePercentageAvg(ConferenceStatQuery query)throws Exception {
				//设置一个组织在时间段内应完成会议的基数
				SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM");
				int quarterValidNum=MeetingParamsBean.REACH_NUM_QUARTER*DateUtil.quarterNum(sdf.parse(query.getSearchBeginDate()), sdf.parse(query.getSearchEndDate()));
				int monthValidNum=MeetingParamsBean.REACH_NUM_MONTH*DateUtil.monthNum(sdf.parse(query.getSearchBeginDate()), sdf.parse(query.getSearchEndDate()));
				query.setSearchQuarterValidNum(quarterValidNum);
				query.setSearchMonthValidNum(monthValidNum);
				
				List<ConferenceStat> list=conferenceStatDao.countConferencePercentageAvg(query);
				
				//每个会议类型的平均完成度 
				DecimalFormat df = new DecimalFormat("0.00%");
				for(ConferenceStat bean:list) {
					ConferenceSynchronous con=bean.getConferenceSynchronous().get(0);
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount1())&&con.getConferenceCount1()>0&&bean.getOrgNum()>0) {
						bean.setZbdyAvgNum((double)con.getConferenceCount1()/(quarterValidNum*bean.getOrgNum()));
						bean.setAvgReachNum1(df.format((double)con.getConferenceCount1()/(quarterValidNum*bean.getOrgNum())));
					}else {
						bean.setAvgReachNum1("0%");
					}
					
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount2())&&con.getConferenceCount2()>0&&bean.getOrgNum()>0) {
						bean.setDkAvgNum((double)con.getConferenceCount2()/(monthValidNum*bean.getOrgNum()));
						bean.setAvgReachNum2(df.format((double)con.getConferenceCount2()/(monthValidNum*bean.getOrgNum())));
					}else {
						bean.setAvgReachNum2("0%");
					}
					
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount3())&&con.getConferenceCount3()>0&&bean.getOrgNum()>0) {
						bean.setDxzAvgNum((double)con.getConferenceCount3()/(monthValidNum*bean.getOrgNum()));
						bean.setAvgReachNum3(df.format((double)con.getConferenceCount3()/(monthValidNum*bean.getOrgNum())));
					}else {
						bean.setAvgReachNum3("0%");
					}
					
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount4())&&con.getConferenceCount4()>0&&bean.getOrgNum()>0) {
						bean.setDzbwyhAvgNum((double)con.getConferenceCount4()/(quarterValidNum*bean.getOrgNum()));
						bean.setAvgReachNum4(df.format((double)con.getConferenceCount4()/(quarterValidNum*bean.getOrgNum())));
					}else {
						bean.setAvgReachNum4("0%");
					}
					
				}
			//修改排序方式,2为按完成度排序
				
				if(Integer.valueOf(2).equals(query.getSearchOrderType())) {
					List<ConferenceStat> list2=new ArrayList<>();
					if(ConferenceStatQuery.ZBDYDH.equals(Integer.valueOf(query.getSearchType()))) {
						//根据avgReachNum从大到小排序
						list2=list.stream()
								.sorted(Comparator.comparing(ConferenceStat::getZbdyAvgNum).reversed())
								.collect(Collectors.toList());
					}else if(ConferenceStatQuery.DK.equals(Integer.valueOf(query.getSearchType()))) {
						list2=list.stream()
								.sorted(Comparator.comparing(ConferenceStat::getDkAvgNum).reversed())
								.collect(Collectors.toList());
					}else if(ConferenceStatQuery.DXZH.equals(Integer.valueOf(query.getSearchType()))) {
						list2=list.stream()
								.sorted(Comparator.comparing(ConferenceStat::getDxzAvgNum).reversed())
								.collect(Collectors.toList());
					}else if(ConferenceStatQuery.ZBWYHHY.equals(Integer.valueOf(query.getSearchType()))) {
						list2=list.stream()
								.sorted(Comparator.comparing(ConferenceStat::getDzbwyhAvgNum).reversed())
								.collect(Collectors.toList());
					}
					return list2;
				}
				
		return list;
	}


	@Override
	public List<ConferenceStat> countConferencePercentageRegion(ConferenceStatQuery query) throws Exception {
		//设置一个组织在时间段内应完成会议的基数
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM");
		int quarterValidNum=MeetingParamsBean.REACH_NUM_QUARTER*DateUtil.quarterNum(sdf.parse(query.getSearchBeginDate()), sdf.parse(query.getSearchEndDate()));
		int monthValidNum=MeetingParamsBean.REACH_NUM_MONTH*DateUtil.monthNum(sdf.parse(query.getSearchBeginDate()), sdf.parse(query.getSearchEndDate()));
		query.setSearchQuarterValidNum(quarterValidNum);
		query.setSearchMonthValidNum(monthValidNum);
		//如果是首页的,取的条数小于实际数据
		int pageSize=query.getPageSize();
		query.setPageSize(-1);
		
		List<ConferenceStat> list=conferenceStatDao.countConferencePercentageAvg(query);
		
		//所有会议平均完成度 
		DecimalFormat df = new DecimalFormat("0.00%");
		for(ConferenceStat bean:list) {
			ConferenceSynchronous con=bean.getConferenceSynchronous().get(0);
			double conferenceCount1=0,conferenceCount2=0,conferenceCount3=0,conferenceCount4=0;
			if(PropertyUtil.objectNotEmpty(con.getConferenceCount1())&&con.getConferenceCount1()>0) conferenceCount1=con.getConferenceCount1();
			if(PropertyUtil.objectNotEmpty(con.getConferenceCount2())&&con.getConferenceCount2()>0) conferenceCount2=con.getConferenceCount2();
			if(PropertyUtil.objectNotEmpty(con.getConferenceCount3())&&con.getConferenceCount3()>0) conferenceCount3=con.getConferenceCount3();
			if(PropertyUtil.objectNotEmpty(con.getConferenceCount4())&&con.getConferenceCount4()>0) conferenceCount4=con.getConferenceCount4();
			double n=((double)conferenceCount1/(quarterValidNum*bean.getOrgNum())
					+(double)conferenceCount2/(monthValidNum*bean.getOrgNum())
					+(double)conferenceCount3/(monthValidNum*bean.getOrgNum())
					+(double)conferenceCount4/(quarterValidNum*bean.getOrgNum())
					)/4;
			bean.setZbdyAvgNum(n);//借用该字段来排序
			bean.setAvgReachNum(df.format(n));
		}
		//放大不分页,1为按组织排序
		if(Integer.valueOf(1).equals(query.getSearchOrderType())) {
			return list;
		}
		//根据avgReachNum从小到大排序
		List<ConferenceStat> list2=list.stream()
				.sorted(Comparator.comparing(ConferenceStat::getZbdyAvgNum))
				.collect(Collectors.toList());
		if(pageSize>-1&&list2.size()>pageSize) {
			List<ConferenceStat> list3=list2.subList(list2.size()-pageSize, list2.size());
			return list3;
		}
		return list2;
	}


	@Override
	public List<ConferenceStat> countConferencePercentageBynum(ConferenceStatQuery query) throws Exception {
		// 查出一共有多少支部
		int orgNum=conferenceStatDao.findOrgNumById(query.getSearchOrganizationID());
		// 查出每个类型的数量分布并算出占比
		DecimalFormat df = new DecimalFormat("0.00%");
		List<ConferenceStat> list=new ArrayList<ConferenceStat>();
		for (int i = 1; i <=4; i++) {
			query.setSearchType(String.valueOf(i));
			ConferenceStat conferenceStat=conferenceStatDao.countConferencePercentageBynum(query);
			if(!PropertyUtil.objectNotEmpty(conferenceStat)) {
				conferenceStat=new ConferenceStat();
				conferenceStat.setConferenceOrgNum1(0);
				conferenceStat.setConferenceOrgNum2(0);
				conferenceStat.setConferenceOrgNum3(0);
				conferenceStat.setConferenceOrgNum4(0);
			}
			conferenceStat.setOrgNum(orgNum);
			conferenceStat.setConferenceType(String.valueOf(i));
			int num1=conferenceStat.getConferenceOrgNum1();
			int num2=conferenceStat.getConferenceOrgNum2();
			int num3=conferenceStat.getConferenceOrgNum3();
			int num4=conferenceStat.getConferenceOrgNum4();
			String [] orgNumPros=new String[5];
			if((num1+num2+num3+num4)>=orgNum) {
				orgNumPros[0]="0%";
			}else {
				orgNumPros[0]=df.format((double)(orgNum-(num1+num2+num3+num4))/orgNum);
			}
			orgNumPros[1]=df.format((double)num1/orgNum);
			orgNumPros[2]=df.format((double)num2/orgNum);
			orgNumPros[3]=df.format((double)num3/orgNum);
			orgNumPros[4]=df.format((double)num4/orgNum);
			conferenceStat.setConferenceOrgNumPro(orgNumPros);//五种占比
			
			list.add(conferenceStat);
		}
		return list;
	}


	@Override
	public List<ConferenceStat> countConferenceFinishOrg(ConferenceStatQuery query) throws Exception {
		//设置一个组织在时间段内应完成会议的基数
				SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM");
				int quarterValidNum=MeetingParamsBean.REACH_NUM_QUARTER*DateUtil.quarterNum(sdf.parse(query.getSearchBeginDate()), sdf.parse(query.getSearchEndDate()));
				int monthValidNum=MeetingParamsBean.REACH_NUM_MONTH*DateUtil.monthNum(sdf.parse(query.getSearchBeginDate()), sdf.parse(query.getSearchEndDate()));
				query.setSearchQuarterValidNum(quarterValidNum);
				query.setSearchMonthValidNum(monthValidNum);
				
				query.setPageSize(-1);
				List<ConferenceStat> list=conferenceStatDao.countConferencePercentageAvg(query);
				List<ConferenceStat> resultList=new  ArrayList<ConferenceStat>();
				for(ConferenceStat bean:list) {
					ConferenceSynchronous con=bean.getConferenceSynchronous().get(0);
					int conferenceCount1=0,conferenceCount2=0,conferenceCount3=0,conferenceCount4=0;
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount1())&&con.getConferenceCount1()>0) conferenceCount1=con.getConferenceCount1();
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount2())&&con.getConferenceCount2()>0) conferenceCount2=con.getConferenceCount2();
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount3())&&con.getConferenceCount3()>0) conferenceCount3=con.getConferenceCount3();
					if(PropertyUtil.objectNotEmpty(con.getConferenceCount4())&&con.getConferenceCount4()>0) conferenceCount4=con.getConferenceCount4();
					if(bean.getOrgNum()>0&&conferenceCount1>=(quarterValidNum*bean.getOrgNum())&&conferenceCount2>=(monthValidNum*bean.getOrgNum())
							&&conferenceCount3>=(monthValidNum*bean.getOrgNum())&&conferenceCount4>=(quarterValidNum*bean.getOrgNum())) {
						resultList.add(bean);
					}
				}
				
		return resultList;
	}


	@Override
	public List<ConferenceStat> findConferencePercentageByOrg(ConferenceStatQuery query) throws Exception {
		
		return conferenceStatDao.findConferencePercentageByOrg(query);
	}
	
}
